# cython: embedsignature=True
# cython: profile=False


from libcpp cimport bool
from posix.unistd cimport uid_t, pid_t
from libc.stdint cimport int32_t, int64_t, uint8_t, uint16_t, uint32_t, uint64_t
from cpython.version cimport PY_MAJOR_VERSION
from posix.unistd cimport uid_t, pid_t, gid_t
from libc.stdint cimport uint32_t, uint16_t, uint64_t


cdef extern from "<netinet/in.h>" nogil:
    ctypedef struct sockaddr_in
    ctypedef struct sockaddr_storage

cdef extern from '<stdio.h>' nogil:
    ctypedef struct FILE
    cdef FILE *stdout


cdef extern from '<Python.h>' nogil:
    cdef FILE *PyFile_AsFile(object file)
    char *__FILE__
    cdef int __LINE__
    char *__FUNCTION__


cdef extern from '<time.h>' nogil:
    ctypedef long time_t


cdef extern from "<netinet/in.h>" nogil:
    ctypedef struct sockaddr_in


cdef extern from "<pthread.h>" nogil:
    ctypedef union pthread_mutex_t


cdef extern from *:
    ctypedef struct slurm_job_credential
    ctypedef struct switch_jobinfo
    ctypedef struct job_resources
    ctypedef struct select_jobinfo
    ctypedef struct select_nodeinfo
    ctypedef struct jobacctinfo
    ctypedef struct allocation_msg_thread
    ctypedef struct sbcast_cred
    ctypedef struct hostlist
    ctypedef struct xlist
    ctypedef struct listIterator
    ctypedef struct slurm_step_ctx_struct
    ctypedef char const_char "const char"
    ctypedef struct slurm_ctl_conf_t
    ctypedef char* const_char_ptr "const char*"
    ctypedef char** const_char_pptr "const char**"


{% include 'jinja2/slurm_errno.h.pxd' %}

{% include 'jinja2/slurm.h.pxd' %}

{% include 'jinja2/slurmdb.h.pxd' %}


#
# PySlurm helper functions
#


cdef inline listOrNone(char* value, sep_char):
    if value is NULL:
        return []

    if not sep_char:
        return value.decode("UTF-8", "replace")

    if sep_char == b'':
        return value.decode("UTF-8", "replace")

    return value.decode("UTF_8", "replace").split(sep_char)


cdef inline stringOrNone(char* value, value2):
    if value is NULL:
        if value2 is '':
            return None
        return "%s" % value2
    return "%s" % value.decode("UTF-8", "replace")


cdef inline int16orNone(uint16_t value):
    if value is NO_VAL16:
        return None
    else:
        return value


cdef inline int32orNone(uint32_t value):
    if value is NO_VAL:
        return None
    else:
        return value


cdef inline int64orNone(uint64_t value):
    if value is NO_VAL64:
        return None
    else:
        return value


cdef inline int16orUnlimited(uint16_t value, return_type):
    if value is INFINITE16:
        if return_type is "int":
            return None
        else:
            return "UNLIMITED"
    else:
        if return_type is "int":
            return value
        else:
            return str(value)


cdef inline boolToString(int value):
    if value == 0:
        return 'False'
    return 'True'


cdef extern char **environ

cdef extern char *slurm_preempt_mode_string (uint16_t preempt_mode)
cdef extern void slurm_make_time_str (time_t *time, char *string, int size)
cdef extern char *slurm_job_state_string (uint16_t inx)
cdef extern char *slurm_job_reason_string (int inx)
cdef extern void slurm_env_array_merge(char ***dest_array, const_char_pptr src_array)
cdef extern char **slurm_env_array_create()
cdef extern int slurm_env_array_overwrite(char ***array_ptr, const_char_ptr name, const_char_ptr value)
cdef extern char *slurm_node_state_string (uint32_t inx)
cdef extern char *slurm_step_layout_type_name (task_dist_states_t task_dist)
cdef extern void slurm_xfree (void **, const_char_ptr, int, const_char_ptr)
cdef extern char *slurm_reservation_flags_string (reserve_info_t *resv_ptr)
cdef extern void slurm_free_stats_response_msg (stats_info_response_msg_t *msg)
cdef extern int slurm_addto_char_list_with_case(List char_list, char *names, bool lower_case_noralization)
cdef extern int slurm_addto_step_list(List step_list, char *names)
cdef extern time_t slurm_parse_time(char *time_str, int past)
cdef extern int slurmdb_report_set_start_end_time(time_t *start, time_t *end)

cdef inline xfree(void *__p):
    slurm_xfree(&__p, __FILE__, __LINE__, __FUNCTION__)
